/**
 * 更新basic_items表ID脚本
 * 功能：根据基础物品_0911.json文件中的ID，更新数据库中的basic_items表ID
 * 确保数据库中的ID与JSON文件中的ID保持一致
 */

const mysql = require('mysql2/promise');
const fs = require('fs');
const path = require('path');

// 数据库连接配置（硬编码）
const DB_CONFIG = {
    host: '43.143.253.188',
    port: 3306,
    user: 'nextjs',
    password: 'yEAiRE2jcxTyRBy5',
    database: 'nextjs',
    charset: 'utf8mb4'
};

class BasicItemsIdUpdater {
    constructor() {
        this.connection = null;
        this.jsonData = null;
        this.updateStats = {
            total: 0,
            matched: 0,
            updated: 0,
            errors: 0
        };
    }

    // 连接数据库
    async connectDatabase() {
        try {
            console.log('🔌 正在连接数据库...');
            this.connection = await mysql.createConnection(DB_CONFIG);
            console.log('✅ 数据库连接成功');
        } catch (error) {
            console.error('❌ 数据库连接失败:', error.message);
            throw error;
        }
    }

    // 关闭数据库连接
    async closeDatabase() {
        if (this.connection) {
            await this.connection.end();
            console.log('🔌 数据库连接已关闭');
        }
    }

    // 加载JSON数据
    loadJsonData() {
        try {
            console.log('📄 正在加载基础物品JSON数据...');
            const jsonPath = path.join(__dirname, 'output', '基础物品_0911.json');

            if (!fs.existsSync(jsonPath)) {
                throw new Error(`JSON文件不存在: ${jsonPath}`);
            }

            const jsonContent = fs.readFileSync(jsonPath, 'utf8');
            this.jsonData = JSON.parse(jsonContent);

            console.log(`✅ JSON数据加载成功，共 ${Object.keys(this.jsonData).length} 条记录`);
        } catch (error) {
            console.error('❌ 加载JSON数据失败:', error.message);
            throw error;
        }
    }

    // 从JSON数据中提取物品名称和ID的映射
    extractNameIdMapping() {
        const nameIdMap = new Map();

        for (const [id, itemData] of Object.entries(this.jsonData)) {
            if (itemData && itemData.data && Array.isArray(itemData.data)) {
                // 查找名称字段
                const nameField = itemData.data.find(field => field.k === '名称:');
                if (nameField && nameField.v) {
                    nameIdMap.set(nameField.v.trim(), parseInt(id));
                }
            }
        }

        console.log(`📊 从JSON中提取到 ${nameIdMap.size} 个物品名称-ID映射`);
        return nameIdMap;
    }

    // 查询数据库中的basic_items表
    async getDatabaseItems() {
        try {
            console.log('🔍 正在查询数据库中的basic_items表...');
            const [rows] = await this.connection.execute(
                'SELECT id, name FROM basic_items ORDER BY id'
            );

            console.log(`✅ 数据库查询成功，共 ${rows.length} 条记录`);
            return rows;
        } catch (error) {
            console.error('❌ 查询数据库失败:', error.message);
            throw error;
        }
    }

    // 更新数据库中的ID（使用临时ID避免冲突）
    async updateItemId(oldId, newId, itemName) {
        try {
            // 如果ID已经匹配，无需更新
            if (oldId === newId) {
                console.log(`ℹ️  物品 "${itemName}" 的ID已经是 ${newId}，无需更新`);
                return true;
            }

            // 首先检查新ID是否已存在
            const [existingRows] = await this.connection.execute(
                'SELECT id, name FROM basic_items WHERE id = ?',
                [newId]
            );

            if (existingRows.length > 0) {
                const existingItem = existingRows[0];
                if (existingItem.name !== itemName) {
                    console.log(`⚠️  ID ${newId} 已被物品 "${existingItem.name}" 占用，跳过更新 "${itemName}"`);
                    return false;
                } else {
                    console.log(`ℹ️  物品 "${itemName}" 的ID已经是 ${newId}，无需更新`);
                    return true;
                }
            }

            // 使用临时ID避免冲突
            const tempId = 999999 + oldId; // 使用大数字作为临时ID

            // 使用query方法执行事务控制语句
            await this.connection.query('START TRANSACTION');

            try {
                // 1. 将当前物品移动到临时ID
                await this.connection.execute(
                    'UPDATE basic_items SET id = ? WHERE id = ?',
                    [tempId, oldId]
                );

                // 2. 将目标ID的物品移动到当前ID（如果存在）
                const [targetRows] = await this.connection.execute(
                    'SELECT id, name FROM basic_items WHERE id = ?',
                    [newId]
                );

                if (targetRows.length > 0) {
                    const targetItem = targetRows[0];
                    await this.connection.execute(
                        'UPDATE basic_items SET id = ? WHERE id = ?',
                        [oldId, newId]
                    );
                    console.log(`🔄 交换ID: "${targetItem.name}" ${newId} → ${oldId}`);
                }

                // 3. 将临时ID的物品移动到目标ID
                await this.connection.execute(
                    'UPDATE basic_items SET id = ? WHERE id = ?',
                    [newId, tempId]
                );

                // 提交事务
                await this.connection.query('COMMIT');

                console.log(`✅ 更新成功: "${itemName}" ID ${oldId} → ${newId}`);
                return true;

            } catch (error) {
                // 回滚事务
                await this.connection.query('ROLLBACK');
                throw error;
            }

        } catch (error) {
            console.error(`❌ 更新失败: "${itemName}" ID ${oldId} → ${newId}`, error.message);
            return false;
        }
    }

    // 执行ID更新流程
    async updateIds() {
        try {
            // 提取JSON中的名称-ID映射
            const nameIdMap = this.extractNameIdMapping();

            // 查询数据库中的物品
            const dbItems = await this.getDatabaseItems();

            console.log('\n🔄 开始更新ID...');
            console.log('=' * 50);

            for (const dbItem of dbItems) {
                this.updateStats.total++;
                const dbName = dbItem.name.trim();
                const dbId = dbItem.id;

                // 在JSON中查找对应的ID
                if (nameIdMap.has(dbName)) {
                    const jsonId = nameIdMap.get(dbName);
                    this.updateStats.matched++;

                    if (dbId !== jsonId) {
                        const success = await this.updateItemId(dbId, jsonId, dbName);
                        if (success) {
                            this.updateStats.updated++;
                        } else {
                            this.updateStats.errors++;
                        }
                    } else {
                        console.log(`ℹ️  物品 "${dbName}" ID已匹配 (${dbId})`);
                    }
                } else {
                    console.log(`⚠️  在JSON中未找到物品: "${dbName}" (数据库ID: ${dbId})`);
                }
            }

            console.log('\n' + '=' * 50);
            console.log('📊 更新统计:');
            console.log(`   总处理数量: ${this.updateStats.total}`);
            console.log(`   匹配成功数量: ${this.updateStats.matched}`);
            console.log(`   实际更新数量: ${this.updateStats.updated}`);
            console.log(`   错误数量: ${this.updateStats.errors}`);

        } catch (error) {
            console.error('❌ 更新过程中发生错误:', error.message);
            throw error;
        }
    }

    // 验证更新结果
    async verifyUpdate() {
        try {
            console.log('\n🔍 正在验证更新结果...');

            const nameIdMap = this.extractNameIdMapping();
            const dbItems = await this.getDatabaseItems();

            let matchCount = 0;
            let mismatchCount = 0;

            for (const dbItem of dbItems) {
                const dbName = dbItem.name.trim();
                const dbId = dbItem.id;

                if (nameIdMap.has(dbName)) {
                    const jsonId = nameIdMap.get(dbName);
                    if (dbId === jsonId) {
                        matchCount++;
                    } else {
                        mismatchCount++;
                        console.log(`❌ ID不匹配: "${dbName}" 数据库ID:${dbId}, JSON ID:${jsonId}`);
                    }
                }
            }

            console.log(`\n📊 验证结果:`);
            console.log(`   匹配数量: ${matchCount}`);
            console.log(`   不匹配数量: ${mismatchCount}`);
            console.log(`   匹配率: ${((matchCount / (matchCount + mismatchCount)) * 100).toFixed(2)}%`);

        } catch (error) {
            console.error('❌ 验证过程中发生错误:', error.message);
        }
    }

    // 运行完整的更新流程
    async runUpdate() {
        console.log('🚀 开始更新basic_items表ID...\n');

        try {
            // 1. 连接数据库
            await this.connectDatabase();

            // 2. 加载JSON数据
            this.loadJsonData();

            // 3. 执行ID更新
            await this.updateIds();

            // 4. 验证更新结果
            await this.verifyUpdate();

            console.log('\n🎉 ID更新流程完成！');

        } catch (error) {
            console.error('💥 更新流程失败:', error.message);
            throw error;
        } finally {
            // 5. 关闭数据库连接
            await this.closeDatabase();
        }
    }
}

// 运行更新
async function main() {
    console.log('🎯 basic_items表ID更新工具');
    console.log('   目标：确保数据库中的ID与基础物品_0911.json中的ID保持一致\n');

    const updater = new BasicItemsIdUpdater();
    await updater.runUpdate();
}

// 如果直接运行此脚本
if (require.main === module) {
    main().catch((error) => {
        console.error('💥 脚本执行失败:', error.message);
        process.exit(1);
    });
}

module.exports = BasicItemsIdUpdater;
